//
// SoapTrace.Net - A soap message monitoring utility. 
//
// Copyright (C) 2004 Matthew Ward
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation; either version 2 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
//
// Matthew Ward (mrward@users.sourceforge.net)

using SoapTrace.Core.Diagnostics;
using System;
using NUnit.Framework;

namespace SoapTrace.Tests
{
	/// <summary>
	/// Tests the <see cref="Logger"/> class and the 
	/// <see cref="LogEntryCollection"/> class.
	/// </summary>
	[ TestFixture ]
	public class LoggerTestFixture
	{
		/// <summary>
		/// The log event handler.
		/// </summary>
		private LogEventHandler m_LogEventHandler;
		
		/// <summary>
		/// Stores log entries generated by the <see cref="Logger.LogEntryAdded"/>
		/// event.
		/// </summary>
		private LogEntryCollection m_LogEntries;
		
		/// <summary>
		/// Initialises each test.
		/// </summary>
		[ SetUp ]
		public void Init( )
		{
			m_LogEntries = new LogEntryCollection( );
			m_LogEntries.CountLimit = 10;
			
			Logger.Level = LogLevel.Debug;
			
			m_LogEventHandler = new LogEventHandler( OnLogEntryAdded );
			Logger.LogEntryAdded += m_LogEventHandler;
		}
		
		/// <summary>
		/// Cleans up after each test.
		/// </summary>
		[ TearDown ]
		public void TearDown( )
		{
			if( m_LogEventHandler != null )
			{
				Logger.LogEntryAdded -= m_LogEventHandler;
			}
		}
		
		/// <summary>
		/// Tests the ring buffer.
		/// </summary>
		[ Test ]
		public void AddInfoLogEntry( )
		{
			string MessageText = "Test";
			
			// Check no entries yet.
			Assert.AreEqual( 0, m_LogEntries.Count, "Should not be any log entries." );
			
			Logger.Log( MessageText );
			
			// Check entry stored.
			Assert.AreEqual( 1, m_LogEntries.Count, "Should be one log entry." );
			LogEntry LogEntry = m_LogEntries[ 0 ];
			Assert.AreEqual( MessageText, LogEntry.Message, "1st added message is incorrect." );
			Assert.AreEqual( LogLevel.Info, LogEntry.Level, "Log level is incorrect." );
		
			// Add another entry.
			
			MessageText = "Another test...";
			
			Logger.Log( MessageText );
			Assert.AreEqual( 2, m_LogEntries.Count, "Should be two log entries." );
			LogEntry = m_LogEntries[ 1 ];
			Assert.AreEqual( MessageText, LogEntry.Message, "2nd added message is incorrect." );
			Assert.AreEqual( LogLevel.Info, LogEntry.Level, "Log level is incorrect." );
		}
		
		/// <summary>
		/// Logs an error.
		/// </summary>
		[ Test ]
		public void LogError( )
		{
			Assert.AreEqual( 0, m_LogEntries.Count, "Should not be any entries." );
			
			string MessageText = "Test";
			Logger.LogError( MessageText );
			
			// Check entry stored.
			Assert.AreEqual( 1, m_LogEntries.Count, "Should be one log entry." );
			LogEntry LogEntry = m_LogEntries[ 0 ];
			Assert.AreEqual( MessageText, LogEntry.Message, "1st added message is incorrect." );
			Assert.AreEqual( LogLevel.Error, LogEntry.Level, "Log level is incorrect." );
		}
		       
		/// <summary>
		/// Logs a warning.
		/// </summary>
		[ Test ]
		public void LogWarning( )
		{
			Assert.AreEqual( 0, m_LogEntries.Count, "Should not be any entries." );
			
			string MessageText = "Test";
			Logger.LogWarning( MessageText );
			
			// Check entry stored.
			Assert.AreEqual( 1, m_LogEntries.Count, "Should be one log entry." );
			LogEntry LogEntry = m_LogEntries[ 0 ];
			Assert.AreEqual( MessageText, LogEntry.Message, "1st added message is incorrect." );
			Assert.AreEqual( LogLevel.Warn, LogEntry.Level, "Log level is incorrect." );
		}	
		
		/// <summary>
		/// Logs a debug message.
		/// </summary>
		[ Test ]
		public void LogDebug( )
		{
			Assert.AreEqual( 0, m_LogEntries.Count, "Should not be any entries." );
			
			string MessageText = "Test";
			Logger.LogDebug( MessageText );
			
			// Check entry stored.
			Assert.AreEqual( 1, m_LogEntries.Count, "Should be one log entry." );
			LogEntry LogEntry = m_LogEntries[ 0 ];
			Assert.AreEqual( MessageText, LogEntry.Message, "1st added message is incorrect." );
			Assert.AreEqual( LogLevel.Debug, LogEntry.Level, "Log level is incorrect." );
		}	
		
		/// <summary>
		/// Checks that log events are generated.
		/// </summary>
		[ Test ]
		public void LogEvents( )
		{
			string MessageText = "Test";
			Logger.LogDebug( MessageText );
			
			// Check entry stored.
			Assert.AreEqual( 1, m_LogEntries.Count, "Should be one log entry." );
			LogEntry LogEntry = m_LogEntries[ 0 ];
			Assert.AreEqual( MessageText, LogEntry.Message, "1st added message is incorrect." );
			Assert.AreEqual( LogLevel.Debug, LogEntry.Level, "1st added message log level is incorrect." );
			
			MessageText = "Test 2";
			Logger.Log( MessageText );
			
			// Check entry stored.
			Assert.AreEqual( 2, m_LogEntries.Count, "Should be one log entry." );
			LogEntry = m_LogEntries[ 1 ];
			Assert.AreEqual( MessageText, LogEntry.Message, "1st added message is incorrect." );
			Assert.AreEqual( LogLevel.Info, LogEntry.Level, "1st added message log level is incorrect." );
		}
		/// <summary>
		/// Tests the limit on the <see cref="LogEntryCollection"/> class.
		/// </summary>	
		[ Test ]
		public void LogEntryCollectionLimit( )
		{
			m_LogEntries.CountLimit = 1;
			
			// Check no entries yet.
			Assert.AreEqual( 0, m_LogEntries.Count, "Should not be any log entries." );
			
			string MessageText = "Test";
			Logger.Log( MessageText );
			
			// Check entry stored.
			Assert.AreEqual( 1, m_LogEntries.Count, "Should be one log entry." );
			LogEntry LogEntry = m_LogEntries[ 0 ];
			Assert.AreEqual( MessageText, LogEntry.Message, "1st added message is incorrect." );
			Assert.AreEqual( LogLevel.Info, LogEntry.Level, "Log level is incorrect." );
		
			// Add another entry.
			
			MessageText = "Another test...";
			
			Logger.LogDebug( MessageText );
			Assert.AreEqual( 1, m_LogEntries.Count, "Should be one log entry." );
			LogEntry = m_LogEntries[ 0 ];
			Assert.AreEqual( MessageText, LogEntry.Message, "2nd added message is incorrect." );
			Assert.AreEqual( LogLevel.Debug, LogEntry.Level, "Log level is incorrect." );
		}
		
		/// <summary>
		/// Tests that setting the log level correcty reduces
		/// the amount of message events being raised.</summary>
		[ Test ]
		public void ChangeLogLevel( )
		{
			Logger.Level = LogLevel.Info;
			
			m_LogEntries.CountLimit = 1;
			
			// Check no entries yet.
			Assert.AreEqual( 0, m_LogEntries.Count, "Should not be any log entries." );
			
			string MessageText = "Debug";
			Logger.LogDebug( MessageText );
			
			// Check no entries yet.
			Assert.AreEqual( 0, m_LogEntries.Count, "Should not be any log entries." );

			MessageText = "Info";
			Logger.Log( MessageText );
			
			// Check entry stored.
			Assert.AreEqual( 1, m_LogEntries.Count, "Should be one log entry." );
			LogEntry LogEntry = m_LogEntries[ 0 ];
			Assert.AreEqual( MessageText, LogEntry.Message, "1st added message is incorrect." );
			Assert.AreEqual( LogLevel.Info, LogEntry.Level, "Log level is incorrect." );
		}
		
		/// <summary>
		/// Log entry handler.
		/// </summary>
		/// <param name="sender">The event source.</param>
		/// <param name="e">The event arguments.</param>
		private void OnLogEntryAdded( object sender, LogEventArgs e )
		{
			m_LogEntries.Add( e.LogEntry );
		}
	}
}
